<?php
namespace Forxx\Api;

use Forxx\Dao\ArtistDTable;
use Forxx\Dao\ArtistNameAliasTable;
use Forxx\Dao\ArtistTable;
use Forxx\Dao\ArtistViewTable;
use Forxx\Dao\AskArtistXTable;
use Forxx\Dao\AskBaseXTable;
use Forxx\Dao\MusicBaseTable;
use Forxx\Api\Utils;
use Forxx\CacheKeys;
use Forxx\RedisCache;
use Lavender\Db\Expression;
use Lavender\Errno;
use Lavender\Exception;
use Lavender\IdMaker;

class Artist
{
    /**
     * 获取列表数据
     * @param array $params
     * @return array
     */
    public static function get($params = [])
    {
        $res = [];

        return $res;
    }

    /**
     * 获取单个数据
     * @param $id
     * @param array $params
     * @return array
     */
    public static function find($id,$params = [])
    {
        $base = ArtistTable::instance()->get([$id]);
        $alias = ArtistNameAliasTable::instance()->get(null,[],['artist_id'=>$id]);
        $count = ArtistViewTable::instance()->get([$id]);
        $posts = ArtistDTable::instance()->get([$id],[],[],'created DESC',0,10);
        $base_ids = array_column($posts,'base_id');
        $asks = AskArtistXTable::instance()->get([$id],[],[],'created DESC',0,10);
        $ask_id = array_column($asks,'ask_id');
        if(!empty($base_ids))
        {
            $bases = MusicBaseTable::instance()->get($base_ids);
            $bases = Utils::sort_by_given_ids($bases,$base_ids);
        }
        else
        {
            $bases = [];
        }
        if(!empty($ask_id))
        {
            $ask_base = AskBaseXTable::instance()->get($ask_id);
            $ask_base = Utils::sort_by_given_ids($ask_base,$ask_id);
        }
        else
        {
            $ask_base = [];
        }

        $relation = [
            'count'=>[Utils::COMPOSITE_BELONG_TO,'id','id'],
            'alias'=>[Utils::COMPOSITE_HAS_MANY,'artist_id','id'],
            'posts'=>[
                'music_base'=>[Utils::COMPOSITE_BELONG_TO,'id','base_id','music_base'],
                Utils::COMPOSITE_HAS_MANY,'artist_id','id','posts'
            ],
            'asks'=>[
                'ask_base'=>[Utils::COMPOSITE_BELONG_TO,'id','ask_id','ask_base'],
                Utils::COMPOSITE_HAS_MANY,'artist_id','id',
            ]
        ];
        $res = Utils::composite_data($base,$relation,[
            'alias'=>$alias,
            'count'=>$count,
            'posts'=>$posts,
            'asks'=>$asks,
            'music_base'=>$bases,
            'ask_base'=> $ask_base
        ]);
        return isset($res[0])?$res[0]:null;
    }

    public static function getPosts($id,$page,$size)
    {
        $base = ArtistTable::instance()->get([$id]);
        $page = intval($page) < 1 ? 10:intval($page);
        $size = intval($size) < 1 ? 10:intval($size);
        $offset = ($page-1) * $size;
        $length = $size;
        $alias = ArtistNameAliasTable::instance()->get(null,[],['artist_id'=>$id]);
        $count = ArtistViewTable::instance()->get([$id]);
        $posts = ArtistDTable::instance()->get([$id],[],[],'created DESC',$offset,$length);
        $base_ids = array_column($posts,'base_id');
		if(!empty($base_ids))
		{
			$bases = MusicBaseTable::instance()->get($base_ids);
			$bases = Utils::sort_by_given_ids($bases,$base_ids);
		}
		else
		{
			$bases = [];
		}

        $relation = [
            'count'=>[Utils::COMPOSITE_BELONG_TO,'id','id'],
            'alias'=>[Utils::COMPOSITE_HAS_MANY,'artist_id','id'],
            'posts'=>[
                'music_base'=>[Utils::COMPOSITE_BELONG_TO,'id','base_id','music_base'],
                Utils::COMPOSITE_HAS_MANY,'artist_id','id','posts'
            ],
        ];
        $res = Utils::composite_data($base,$relation,[
            'alias'=>$alias,
            'count'=>$count,
            'posts'=>$posts,
            'music_base'=>$bases,
        ]);
        return isset($res[0])?$res[0]:null;
    }

    public static function getAsks($id,$page,$size)
    {
        $base = ArtistTable::instance()->get([$id]);
        $page = intval($page) < 1 ? 10:intval($page);
        $size = intval($size) < 1 ? 10:intval($size);
        $offset = ($page-1) * $size;
        $length = $size;
        $alias = ArtistNameAliasTable::instance()->get(null,[],['artist_id'=>$id]);
        $count = ArtistViewTable::instance()->get([$id]);
        $asks = AskArtistXTable::instance()->get([$id],[],[],'created DESC',$offset,$length);
        $ask_id = array_column($asks,'ask_id');
        $ask_base = AskBaseXTable::instance()->get($ask_id);
        $ask_base = Utils::sort_by_given_ids($ask_base,$ask_id);

        $relation = [
            'count'=>[Utils::COMPOSITE_BELONG_TO,'id','id'],
            'alias'=>[Utils::COMPOSITE_HAS_MANY,'artist_id','id'],
            'asks'=>[
                'ask_base'=>[Utils::COMPOSITE_BELONG_TO,'id','ask_id','ask_base'],
                Utils::COMPOSITE_HAS_MANY,'artist_id','id',
            ]
        ];
        $res = Utils::composite_data($base,$relation,[
            'alias'=>$alias,
            'count'=>$count,
            'asks'=>$asks,
            'ask_base'=> $ask_base
        ]);
        return isset($res[0])?$res[0]:null;
    }

    public static function getAll()
    {
        $artists = ArtistTable::instance()->get(null);
        $aliasName = ArtistNameAliasTable::instance()->get(null);
        $count = ArtistViewTable::instance()->get(null);
        $res = Utils::composite_data($artists,[
            'alias'=>[Utils::COMPOSITE_HAS_MANY,'artist_id','id'],
            'count'=>[Utils::COMPOSITE_BELONG_TO,'id','id'],
        ],[
            'alias' =>$aliasName,
            'count' => $count,
        ]);
        return $res;
    }

    /**
     * @param $id
     * @param string $field
     * @throws \Lavender\Dao\Exception
     */
    public static function addCount($id,$field = 'view')
    {
        $now = Utils::get_time();
        ArtistViewTable::instance()->increment($id,[$field=>1],['updated'=>$now],['created'=>$now,'updated'=>$now]);
     }

    /**
     * @param $name
     * @param $page
     * @param $size
     * @return array
     * @throws \Lavender\Db\Exception
     */
    public static function search($name,$page,$size)
    {
        $res = ArtistNameAliasTable::instance()->get([],['artist_id','name'],[Expression::MakeLike('name',$name)],'artist ASC',($page - 1)*$size,$size);
        return $res;
    }

    /**
     * 新增歌手
     * @param array $params
     * @return int
     * @throws Exception
     */
    public static function create($params = [])
    {
        if(!isset($params['name']))
        {
            throw new Exception("bad params",Errno::PARAM_INVALID);
        }
        $name = $params['name'];
        $name = Tag::makeBetterWord($name);
        $artist_id = self::getArtistByAlias($name);
        if(!empty($artist_id))
        {
            return $artist_id;
        }
        $id = IdMaker::make('music_artist');
        $now = Utils::get_time();
        $record = [
            'name' => $name,
            'is_hot' => isset($params['is_hot'])?intval($params['is_hot']):ArtistTable::IS_HOT_DEFAULT,
            'sex' => isset($params['sex'])?intval($params['sex']):ArtistTable::SEX_DEFAULT,
            'area' => isset($params['area'])?intval($params['area']):ArtistTable::AREA_DEFAULT,
            'created'=>$now,
            'updated'=>$now,
        ];
        ArtistTable::instance()->add($id,$record);
        $aliasRecord = [
            'name' => $name,
            'artist_id' => $id,
            'created'=> $now,
        ];
        ArtistNameAliasTable::instance()->add(null,$aliasRecord);

        //删除缓存
        $cacheKey = CacheKeys::MUSIC_ARTIST_LIST;
        RedisCache::instance()->delete($cacheKey);
        return $id;
    }

    /**
     * 修改记录
     * @param $id
     * @param array $params
     */
    public static function update($id,$params = [])
    {

    }

    /**
     * 删除记录
     * @param $id
     * @param array $params
     */
    public static function delete($id,$params = [])
    {
        
    }

    /**
     * 合并两个歌手信息(用于多个别名的情况)
     * @param $toName
     * @param $fromName
     */
    public static function merge($toName,$fromName)
    {

    }

    /**
     * @param $ids
     * @return array
     */
    public static function getArtists($ids)
    {
        $artists = self::getAllArtists();
        $res = [];
        foreach($ids as $id)
        {
            if(isset($artists[$id]))
            {
                $res[$id] = $artists[$id];
            }
        }
        return $res;
    }

    /**
     * 获取所有歌手 [['id'=>123,'name'=>"dfsd"],['id'=>456,'name'=>''],..]
     * @return array
     */
    public static function getAllArtistList()
    {
        $cacheKey = CacheKeys::MUSIC_ARTIST_LIST;
        $artists = RedisCache::instance()->get($cacheKey);
        if(empty($artists))
        {
            $artists = ArtistTable::instance()->get(null,['id','name']);
            RedisCache::instance()->set($cacheKey,$artists,864000);
        }
        return $artists;
    }

    /**
     * 获取所有歌手 [123=>'',456=>'456']
     * @return array
     */
    public static function getAllArtists()
    {
        $artists = self::getAllArtistList();
        return array_combine(Utils::get_column_array('id',$artists),Utils::get_column_array('name',$artists));
    }



    /**
     * 歌手别名搜索
     * @param $aliasName
     * @return string|bool
     */
    public static function getArtistByAlias($aliasName)
    {
        $artists = self::getAllArtists();
        if(($key = array_search($aliasName,$artists)) != false)
        {
            return  $key;
        }
        else
        {
            $records = ArtistNameAliasTable::instance()->get(null,['id','artist_id','name'],['name' =>$aliasName],null,0,1);
            if(empty($records))
            {
                return null;
            }
            else
            {
                $artist_id = $records[0]['artist_id'];
                return $artist_id;
            }
        }
        return false;
    }
}
